package com.vectz.mgt.action;

import java.io.IOException;
import java.util.ArrayList;
import java.util.Hashtable;

import com.vectz.mgt.model.Entity;
import com.vectz.mgt.model.EntityOverview;
import com.vectz.mgt.util.Constant;
import com.vectz.mgt.util.Log;
import com.vectz.mgt.util.Util;

/**
 * @author ai-t.vn
 * 
 */
public class JsfResultCodegenAction {
	ArrayList<Entity> listField = null;
	EntityOverview table = null;
	String outputFolder = "";
	private Hashtable<String, String> fieldFileUpload = new Hashtable<String, String>();
	
	public JsfResultCodegenAction(ArrayList<Entity> listField,
			EntityOverview table, String outputFolder) throws Exception {
		this.listField = listField;
		this.table = table;
		this.outputFolder = outputFolder;
		genernateJsfFile();
	}

	/*
	 * Generate jsf file
	 */
	public void genernateJsfFile() throws Exception {
			String tmplFormContent = Util.readTextFileContent(Util.getTmplPath(
					"jsf", "Form-ResultEntity.txt"));
			String tmplFieldContent = Util.readTextFileContent(Util
					.getTmplPath("jsf", "ConfirmEntity.txt"));

			buildFileUploadName();
			// add content path
			String listFieldForm = genernateFieldForm(listField,
					tmplFieldContent);
			tmplFormContent = tmplFormContent.replaceAll("xxxxFormId", Util.isEmpty(table
					.getScreenId())? table.getName():table.getScreenId());
			tmplFormContent = tmplFormContent.replace("xxxxBodyContent",
					listFieldForm);
			tmplFormContent = tmplFormContent.replaceAll("xxxxInitModify", Util
					.buildButtonAction(table.getName(), "initModify"));
			tmplFormContent = tmplFormContent.replaceAll("xxxxEntityId",
					getIdField(listField));
			
			tmplFormContent = tmplFormContent.replaceAll("xxxxAction", Util
					.lowerCaseFirstChar(table.getName())
					+ "Action");
			
			tmplFormContent = tmplFormContent.replaceAll("xxxxEntityList",
					new StringBuilder().append("/").append(
							Util.getWebbaseDir(table.getDestScreenPath()))
							.append("/").append(
									Util.lowerCaseFirstChar(table.getName()))
							.append("List.xhtml").toString());

			String fileLocation = new StringBuffer().append(outputFolder)
					.append(System.getProperty("file.separator")).append(
							"WebContent").append(
							System.getProperty("file.separator")).append(
							Util.getWebbaseDir(table.getDestScreenPath()))
					.append(System.getProperty("file.separator")).append(
							"result").append(table.getName()).append(".xhtml")
					.toString();

			Util.writeJavaFile(fileLocation, tmplFormContent);
			Log.log("Finish generate jsf file to:" + fileLocation);
	}

	/*
	 * Generate list field name
	 */
	public String genernateFieldForm(ArrayList<Entity> listField,
			String tmplContent) {
		StringBuffer content = new StringBuffer();

		if (listField == null && listField.size() == 0)
			return "";
		Entity field = null;
		for (int i = 0; i < listField.size(); i++) {
			field = (Entity) listField.get(i);
			// check only display=show then add new component
			String tmp = "";
			if (field.getDisplay().equalsIgnoreCase("show")) {
				
				// check if inputDataType = DateTime
				// Modify by anhdv 2008-10-21
				if (field.getInputType().equalsIgnoreCase("DateTime")) {
					tmp = new StringBuffer()
					.append("<tr><td class=\"title\" colspan=\"2\"><h:outputText value=\"")
					.append(field.getScreenName()+"\" /></td>")
					.append("<td>")
					.append("<gmt:periodDateTime id=\"_"+ field.getName() + "\" value=\"")
					.append(getInputValue(field)).append("\" labelFlg=\"true\" required=\"true\"/>")
					.append("</td></tr>").toString();
				}
				
				/* Check if form has fileUpload component then add download link	
				 * Modify by anhdv 2008-10-23
				 */ 
				else if (field.getInputType().equalsIgnoreCase("fileUpload")) {
					tmp = new StringBuffer()
							.append("<tr><td class=\"title\" colspan=\"2\"><h:outputText value=\"")
							.append(field.getScreenName()+"\" /></td>")
							.append("<td>")
							//ex: <h:commandLink value="download" action="/sampleTestDownload/download?index=1" />
							.append("<c:if test=\"${"+ Util.lowerCaseFirstChar(table.getName())
									+ "Action.mode!='DELETE'}\">")
							.append("<c:if test=\"${not empty "+ Util.lowerCaseFirstChar(table.getName())
									+ "Action.fileName"+ fieldFileUpload.get(field.getName()) +"}\">")
							.append("<h:commandLink value=\"download\" action=\"/")
							.append(Util.lowerCaseFirstChar(table.getName()))
							.append("Download/download?index=")
							.append(fieldFileUpload.get(field.getName())+"\" />")
							.append("</c:if>")
							.append("</c:if>")
							.append("</td></tr>").toString();
				}
			
				/* Check if inputType = inputTextArea then display inputTextArea in confirm form
				 * (but not allow edit in this text area) 
				 * Modify at 2008-10-28 by anhdv 
				*/
				else if (field.getInputType().equalsIgnoreCase("inputTextarea")) {
					tmp = new StringBuffer()
							.append("<tr><td class=\"title\" colspan=\"2\"><h:outputText value=\"")
							.append(field.getScreenName()+"\" /></td>")
							.append("<td>")
							.append("<h:inputTextarea size=\""+ field.getScreenLength()+"\" value=\"")
							.append(getInputValue(field)+"\" readonly=\"true\"/>")
							.append("</td></tr>").toString();
				}				
				else {
					tmp = tmplContent;
					tmp = tmp.replaceAll("xxxxLableName", field.getLogicalName());
					// if inputType is selectManyCheckbox then add tag<ui:repeat>
					// Modify by anhdv 2008-10-20
					if (field.getInputType() != null
							&& field.getInputType().equalsIgnoreCase(
									"selectManyCheckbox")) {
						// start <ui:repeat>
						tmp = tmp.replaceAll("xxxxStartRepeat",
								new StringBuffer()
										.append("<ui:repeat value=\"").append(
												getInputValue(field)).append(
												"\" var=\"item\"><li>")
										.toString());
						// loop content
						tmp = tmp.replaceAll("xxxxInputValue", "#{item}");
						// end <ui:repeat>
						tmp = tmp.replaceAll("xxxxEndRepeat",
								"</li></ui:repeat>");

						tmp = tmp.replaceAll("xxxxFormatItem", "");
					} else {
						tmp = tmp.replaceAll("xxxxStartRepeat", "");
						tmp = tmp.replaceAll("xxxxEndRepeat", "");
						tmp = tmp.replaceAll("xxxxInputValue",
								getInputValue(field));
						// check if inputDataType = Time then convert to HH:mm pattern
						if (field.getInputType().equalsIgnoreCase("Time")) {
							tmp = tmp
									.replaceAll("xxxxFormatItem",
											"<s:convertDateTime pattern=\"HH:mm\" type=\"time\" />");
						}
						// check if inputDataType = Date then convert to datetime pattern
						else if (field.getInputType().equalsIgnoreCase("Date")) {
							if (!Util.isEmpty(field.getDescription()))
								tmp = tmp.replaceAll("xxxxFormatItem",
										"<f:convertDateTime pattern=\""
												+ field.getDescription()
												+ "\"/>");
							else
								// default format date: YYYY/MM/DD
								tmp = tmp
										.replaceAll("xxxxFormatItem",
												"<f:convertDateTime pattern=\"yyyy/MM/dd\"/>");
						} else {
							tmp = tmp.replaceAll("xxxxFormatItem", "");
						}
					}
				}
				content.append(tmp);
			}
		}

		return content.toString();
	}

	/*
	 * Generate Id field in model class
	 */
	public String getIdField(ArrayList<Entity> listField) {
		if (listField == null && listField.size() == 0)
			return "";
		Entity field = null;
		for (int i = 0; i < listField.size(); i++) {
			field = (Entity) listField.get(i);
			if (field.getKeyType().equalsIgnoreCase("PK")) {
				return new StringBuffer().append(
						Util.lowerCaseFirstChar(table.getName())).append(
						"Action.").append(
						Util.lowerCaseFirstChar(table.getName())).append(".")
						.append(field.getName()).toString();
			}
		}
		return "";
	}
	
	/**
	 * Put field name with index of file upload (start from 1).
	 */
	public void buildFileUploadName(){
		int num = 0;
		if (listField != null) {
			Entity field = null;
			for (int i = 0; i < listField.size(); i++) {
				field = (Entity) listField.get(i);
				if(field.getInputType()!=null){
					if (field.getInputType().equalsIgnoreCase("fileUpload")){
						num++;
						fieldFileUpload.put(field.getName(),String.valueOf(num));
					}	
				}
			}
		}
	}

	/**
	 * Get input value with pattern: #{entityAction.entity.field}
	 * 
	 * @param entity
	 * @return input value
	 */
	public String getInputValue(Entity entity) {
		return new StringBuffer().append("#{").append(
				Util.lowerCaseFirstChar(table.getName())).append("Action.")
				.append(Util.lowerCaseFirstChar(table.getName())).append(".")
				.append(Util.lowerCaseFirstChar(entity.getName())).append("}")
				.toString();
	}
}
